/*
 * @Description: 通用 Java 解密操作监控脚本 (最终版)。
 *               通过 Hook javax.crypto.Cipher，专门用于捕获并解析验证码的最终解密过程。
 */

console.log("[*] 最终解密监控脚本已启动...");

Java.perform(function() {
    console.log("[*] 正在 Hook javax.crypto.Cipher...");

    const Cipher = Java.use('javax.crypto.Cipher');

    // 辅助函数：将 byte[] 转换为十六进制字符串，方便观察
    function bytesToHex(arr) {
        if (!arr) return "null";
        let hexStr = "";
        for (let i = 0; i < arr.length; i++) {
            let hex = (arr[i] & 0xFF).toString(16);
            hex = (hex.length === 1) ? '0' + hex : hex;
            hexStr += hex;
        }
        return hexStr;
    }

    // 辅助函数：将 byte[] 尝试转换为 UTF-8 字符串
    function bytesToString(arr) {
        if (!arr) return "null";
        try {
            // 使用 Java 的 String 类来处理字节到字符串的转换，更健壮
            return Java.use("java.lang.String").$new(arr, "UTF-8");
        } catch (e) {
            return "[无法转换为字符串]";
        }
    }
    
    // Hook Cipher.getInstance 来获取算法名称
    Cipher.getInstance.overload('java.lang.String').implementation = function(transformation) {
        // 在后台保存算法信息，供 doFinal 使用
        this.transformation = transformation;
        // 调用原始方法
        return this.getInstance(transformation);
    };

    // Hook Cipher.init 来获取解密模式、密钥和IV
    const initOverloads = Cipher.init.overloads;
    for (let i = 0; i < initOverloads.length; i++) {
        initOverloads[i].implementation = function(...args) {
            // 我们只关心解密模式
            const opmode = args[0];
            if (opmode === 2) { // 2 代表 DECRYPT_MODE
                console.log("\n==================== 发现解密操作 (Cipher.init) ====================");
                console.log(`  [算法]: ${this.transformation}`);
                console.log("  [模式]: 解密 (DECRYPT_MODE)");

                // 打印密钥
                const key = args[1];
                if (key) {
                    const keyBytes = key.getEncoded();
                    console.log(`  [密钥 Key (Hex)]: ${bytesToHex(keyBytes)}`);
                }

                // 打印 IV (如果存在)
                if (args.length > 2 && args[2]) {
                    const spec = args[2];
                    // IvParameterSpec 或 GCMParameterSpec 都有 getIV 方法
                    if (spec.getIV) {
                        const ivBytes = spec.getIV();
                         console.log(`  [初始向量 IV (Hex)]: ${bytesToHex(ivBytes)}`);
                    }
                }
                 console.log("======================================================================\n");
            }
            // 调用原始的 init 方法
            return this.init(...args);
        }
    }

    // Hook doFinal, 这是执行解密的核心方法
    const doFinalOverloads = Cipher.doFinal.overloads;
    for (let i = 0; i < doFinalOverloads.length; i++) {
        doFinalOverloads[i].implementation = function(...args) {
            // 调用原始的 doFinal 方法获取解密结果
            const result = this.doFinal(...args);

            // getIV() 存在说明是加密模式，我们不关心。我们只关心解密模式的输出。
            // Cipher 在解密模式下通常 getIV() 会返回 null 或者没有这个方法。
            // 一个简单的判断：如果 Cipher 对象里有 transformation 属性，说明是我们 getInstance hook 过的。
            if (this.transformation) {
                // 输入数据 (args[0] 通常是待解密的 byte[])
                const inputData = args.length > 0 ? args[0] : null;

                console.log("\n==================== 捕获到解密输出 (Cipher.doFinal) ====================");
                console.log(`  [算法]: ${this.transformation}`);
                console.log(`  [->] 解密前数据 (Hex): ${bytesToHex(inputData)}`);

                // 重点：打印解密后的明文！
                console.log("\n  [<-] ✨✨✨ 解密后明文 (String) ✨✨✨:");
                const plaintext = bytesToString(result);
                console.log(plaintext);
                console.log("[+]===result:" + result);

                // 再次尝试将明文作为JSON格式化输出，这通常会成功！
                try {
                    console.log("\n  [<-] ✨✨✨ 解密后明文 (格式化JSON) ✨✨✨:");
                    const jsonObj = JSON.parse(plaintext);
                    console.log(JSON.stringify(jsonObj, null, 2));
                } catch (e) {
                    console.log("  [提示] 解密结果不是一个有效的JSON字符串。");
                }
                console.log("=========================================================================\n");
            }
            
            return result;
        };
    }

    console.log("[*] 通用 Cipher Hook 已全部安装。请操作App以触发滑块验证码。");
});